"""
LLM服务 - 处理对话和消息的数据库操作
"""
from typing import List, Optional, AsyncGenerator
from sqlalchemy.orm import Session
from sqlalchemy import func
from app.models.chat_conversation import ChatConversation
from app.models.chat_message import ChatMessage
from app.models.llm_model import LLMModel
from app.services.ai_service import AIService, ChatMessage as AIChatMessage, AIModelConfig
from app.core.logging import get_logger

logger = get_logger(__name__)


class LLMService:
    """LLM服务类"""
    
    def __init__(self):
        self.ai_service = AIService()
    
    async def create_conversation(
        self, 
        db: Session, 
        user_id: int, 
        title: str, 
        model_id: int
    ) -> ChatConversation:
        """创建新对话"""
        conversation = ChatConversation(
            user_id=user_id,
            title=title,
            model_id=model_id,
            is_active=True
        )
        db.add(conversation)
        db.commit()
        db.refresh(conversation)
        return conversation
    
    async def generate_chat_response(
        self,
        db: Session,
        conversation_id: int,
        user_message: str,
        stream: bool = False
    ) -> str | AsyncGenerator[str, None]:
        """生成聊天响应"""
        # 获取对话信息
        conversation = db.query(ChatConversation).filter(
            ChatConversation.id == conversation_id
        ).first()
        
        if not conversation:
            raise ValueError("对话不存在")
        
        # 获取模型信息
        model = db.query(LLMModel).filter(
            LLMModel.id == conversation.model_id
        ).first()
        
        if not model:
            raise ValueError("模型不存在")
        
        # 保存用户消息
        user_msg = ChatMessage(
            conversation_id=conversation_id,
            role="user",
            content=user_message,
            is_deleted=False
        )
        db.add(user_msg)
        db.commit()
        
        # 获取对话历史
        messages = db.query(ChatMessage).filter(
            ChatMessage.conversation_id == conversation_id,
            ChatMessage.is_deleted == False
        ).order_by(ChatMessage.created_at.asc()).all()
        
        # 转换为AI服务格式
        ai_messages = []
        for msg in messages:
            ai_messages.append(AIChatMessage(
                role=str(msg.role) if msg.role is not None else "user",  # 类型转换
                content=str(msg.content) if msg.content is not None else ""  # 类型转换
            ))
        
        try:
            # 创建AI模型配置，包含API密钥和基础URL
            # 安全地处理模型属性
            provider = str(model.provider) if model.provider is not None else "openai"
            model_name = str(model.model_name) if model.model_name is not None else "gpt-3.5-turbo"
            
            # 处理温度参数
            if isinstance(model.temperature, dict):
                temp_default = model.temperature.get('default', 0.7)
                try:
                    temperature = float(temp_default) if temp_default is not None else 0.7
                except (ValueError, TypeError):
                    temperature = 0.7
            else:
                # 安全地转换SQLAlchemy列到float
                temp_value = model.temperature
                if hasattr(temp_value, 'value'):
                    temp_value = temp_value.value
                try:
                    temperature = float(temp_value) if temp_value is not None else 0.7  # type: ignore
                except (ValueError, TypeError):
                    temperature = 0.7
            
            # 处理最大token数
            # 安全地转换SQLAlchemy列到int
            max_tokens_value = model.max_tokens
            if hasattr(max_tokens_value, 'value'):
                max_tokens_value = max_tokens_value.value
            try:
                max_tokens = int(max_tokens_value) if max_tokens_value is not None else 4000  # type: ignore
            except (ValueError, TypeError):
                max_tokens = 4000
            
            # 处理API密钥和基础URL
            # 安全地转换SQLAlchemy列到str
            api_key_value = model.api_key
            if hasattr(api_key_value, 'value'):
                api_key_value = api_key_value.value
            api_key = str(api_key_value) if api_key_value is not None else None
            
            base_url_value = model.base_url
            if hasattr(base_url_value, 'value'):
                base_url_value = base_url_value.value
            base_url = str(base_url_value) if base_url_value is not None else None
            
            ai_config = AIModelConfig(
                provider=provider,
                model_name=model_name,
                temperature=temperature,
                max_tokens=max_tokens,
                api_key=api_key,
                base_url=base_url,
                stream=stream
            )
            
            # 调用AI服务
            if stream:
                # 流式响应
                response_generator = await self.ai_service.chat_with_config(
                    messages=ai_messages,
                    config=ai_config
                )
                
                # 创建一个生成器来收集完整响应并保存到数据库
                async def response_with_save():
                    full_response = ""
                    # 确保response_generator是异步生成器
                    if hasattr(response_generator, '__aiter__'):
                        async for chunk in response_generator:  # type: ignore
                            chunk_str = str(chunk)
                            full_response += chunk_str
                            yield chunk_str
                    else:
                        # 如果不是生成器，直接返回响应
                        resp_str = str(response_generator)
                        yield resp_str
                    
                    # 保存助手响应
                    assistant_msg = ChatMessage(
                        conversation_id=conversation_id,
                        role="assistant",
                        content=full_response,
                        is_deleted=False
                    )
                    db.add(assistant_msg)
                    db.commit()
                
                return response_with_save()
            else:
                # 非流式响应
                response = await self.ai_service.chat_with_config(
                    messages=ai_messages,
                    config=ai_config
                )
                
                # 保存助手响应
                response_str = str(response) if response is not None else ""
                assistant_msg = ChatMessage(
                    conversation_id=conversation_id,
                    role="assistant",
                    content=response_str,
                    is_deleted=False
                )
                db.add(assistant_msg)
                db.commit()
                
                return response_str
                
        except Exception as e:
            logger.error(f"AI服务调用失败: {str(e)}")
            # 保存错误响应
            error_msg = ChatMessage(
                conversation_id=conversation_id,
                role="assistant",
                content=f"抱歉，我遇到了一些问题：{str(e)}",
                is_deleted=False
            )
            db.add(error_msg)
            db.commit()
            
            if stream:
                async def error_generator():
                    yield f"抱歉，我遇到了一些问题：{str(e)}"
                return error_generator()
            else:
                return f"抱歉，我遇到了一些问题：{str(e)}"
    
    async def count_conversation_tokens(self, db: Session, conversation_id: int) -> int:
        """计算对话的token数量（简化估算）"""
        messages = db.query(ChatMessage).filter(
            ChatMessage.conversation_id == conversation_id,
            ChatMessage.is_deleted == False
        ).all()
        
        total_chars = sum(len(str(msg.content)) if msg.content is not None else 0 for msg in messages)
        # 简化估算：平均4个字符约等于1个token
        estimated_tokens = total_chars // 4
        return estimated_tokens